﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Reflection;
using System.Text;
using System.Threading.Tasks;
using AutoMapper;
using FluentNHibernate.Testing;
using Microsoft.VisualStudio.TestTools.UnitTesting;
using Moq;
using YasharEl.Infrastructure.Core.PersistenceModel.NHibernate.Prototype.Mappings;
using YasharEl.Infrastructure.Core.Personification;
using YasharEl.Infrastructure.ProcessEngine.EntityModel;
using YasharEl.Infrastructure.ProcessEngine.PersistenceModel.NHibernate.Mappings;
using YasharEl.Infrastructure.ProcessEngine.PersistenceModel.NHibernate.Tests.Support;

namespace YasharEl.Infrastructure.ProcessEngine.PersistenceModel.NHibernate.Tests
{
    [TestClass]
    public class ProcessMappingTest : InMemoryDatabaseTest
    {
        public ProcessMappingTest()
            : base
            (
                new Assembly[] 
                { 
                    typeof(ProcessDefinitionEntityMap).Assembly, 
                    typeof(PropertyDefinitionEntityMap).Assembly 
                }
            )
        {

        }

        [TestMethod]
        public void CanCorrectlyMapProcess()
        {
            Mapper.CreateMap<ProcessDefinitionEntityProxy, ProcessDefinitionEntity>()
                .ForMember
                (
                    entity => entity.ProcessDefinitionId,
                    mapper => mapper.MapFrom(result => result.ProcessDefinitionId)
                )
                .ForMember
                (
                    entity => entity.Name,
                    mapper => mapper.MapFrom(result => result.Name)
                )
                .ForMember
                (
                    entity => entity.Description,
                    mapper => mapper.MapFrom(result => result.Description)
                )
                .ForMember
                (
                    entity => entity.SLA,
                    mapper => mapper.MapFrom(result => result.SLA)
                )
                .ForMember
                (
                    entity => entity.WorkflowXaml,
                    mapper => mapper.MapFrom(result => result.WorkflowXaml)
                );

            Mapper.CreateMap<ProcessParticipantEntityProxy, ProcessParticipantEntity>()
                .ForMember
                (
                    entity => entity.Email,
                    mapper => mapper.MapFrom(result => result.Email)
                )
                .ForMember
                (
                    entity => entity.ParticipantId,
                    mapper => mapper.MapFrom(result => result.ParticipantId)
                )
                .ForMember
                (
                    entity => entity.UserName,
                    mapper => mapper.MapFrom(result => result.UserName)
                );

            ProcessDefinitionEntity processDefinitionEntity = Mapper.Map<ProcessDefinitionEntityProxy, ProcessDefinitionEntity>(
                new ProcessDefinitionEntityProxy(1, "InfrastructureTestProcess", "Infrastructure Test Process", 7, @"Tests\InfrastructureTestProcess")
            );

            ProcessParticipantEntity participant = Mapper.Map<ProcessParticipantEntityProxy, ProcessParticipantEntity>(
                new ProcessParticipantEntityProxy(1, "dmitry.khaymov@gmail.com", "Khaymov", "Dmitry")
            );

            new PersistenceSpecification<ProcessEntity>(session)
                .CheckProperty(c => c.ProcessId, (long)1)
                .CheckProperty(c => c.WorkflowInstanceId, new Guid("F2012798-4EB6-4885-A223-D1F868292DAB"))
                .CheckProperty(c => c.CreatedDate, DateTime.Now.AddDays(-7).TruncateToSeconds())
                .CheckProperty(c => c.ProcessPriority, ProcessPriority.High)
                .CheckProperty(c => c.ProcessStatus, ProcessStatus.Active)
                .CheckProperty(c => c.ClosedDate, null)
                .CheckProperty(c => c.ExpiredDate, DateTime.Now.AddDays(7).TruncateToSeconds())
                .CheckProperty(c => c.ModifiedDate, DateTime.Now.TruncateToSeconds())
                .CheckProperty(c => c.StartedDate, DateTime.Now.AddDays(-7).TruncateToSeconds())
                .CheckReference(c => c.ProcessDefinition, processDefinitionEntity)
                .CheckReference(c => c.CreatedBy, participant)
                .CheckReference(c => c.Owner, participant)
                .CheckReference(c => c.ModifiedBy, participant)
                .VerifyTheMappings();
        }
    }
}

